<?php

use EasyWaf\Enums;
use EasyWaf\Utils;

/**
 * 检测IP是否为SEO蜘蛛,如果是,则添加白名单,如果不是,则拉入防火墙
 * 请根据具体业务需求修改代码,Supervisor守护进程运行即可
 */
require '../vendor/autoload.php';

// 输出信息:Supervisor识别启动需要
echo 'EASY_WAF_IP_CHECK程序已启动' . PHP_EOL;

// 连接Redis
$redis = new Redis();
$redis->connect('127.0.0.1');

// IP白名单和黑名单有效期
$expire = 86400 * 365;

// 读取队列数据
while (true) {
    // 读取Ip
    $ipData = $redis->brPop(Enums::WafCheckIpDnsQueueKey, 15);
    if (!$ipData) {
        continue;
    }
    $ip = $ipData['1'];
    echo '正在检查IP: ' . $ip . PHP_EOL;
    // 如果IP在白名单,跳过
    $ipWhiteKey = Utils::getIpCacheKey($ip, Enums::WafIpWhiteListKey);
    if ($redis->get($ipWhiteKey)) {
        echo '此IP: ' . $ip . '命中白名单,跳过' . PHP_EOL;
        continue;
    }

    // 如果IP在黑名单,跳过
    $ipBlackKey = Utils::getIpCacheKey($ip, Enums::WafIpBlackListKey);
    if ($redis->get($ipBlackKey)) {
        echo '此IP: ' . $ip . '命中黑名单,跳过' . PHP_EOL;
        continue;
    }

    // 查询IP-DNS信息
    $checkIpCount = 3;
    $dns = '';
    while ($checkIpCount--) {
        $dns = Utils::reverseDnsLookup($ip);
        if ($dns) {
            break;
        }
    }

    // 根据IP查询结果处理
    if (!$dns) {
        echo '此IP: ' . $ip . '查询DNS失败,已添加黑名单' . PHP_EOL;
        $redis->setex($ipBlackKey, $expire, true);
    } else {
        if (!Utils::isSeoFriendlyDns($dns)) {
            // IP黑名单
            echo '此IP: ' . $ip . '伪造SEO蜘蛛,已添加黑名单' . PHP_EOL;
            $redis->setex($ipBlackKey, $expire, true);
        } else {
            // IP白名单
            echo '此IP: ' . $ip . '为真正的SEO蜘蛛,已添加白名单' . PHP_EOL;
            $redis->setex($ipWhiteKey, $expire, true);
        }
    }
}